package com.hsj.common.gateway.service.impl;

import com.hsj.common.gateway.constants.Constants;
import com.hsj.common.gateway.dao.GatewayDao;
import com.hsj.common.gateway.entity.GatewayDo;
import com.hsj.common.gateway.service.GatewayService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cloud.gateway.event.RefreshRoutesEvent;
import org.springframework.cloud.gateway.filter.FilterDefinition;
import org.springframework.cloud.gateway.handler.predicate.PredicateDefinition;
import org.springframework.cloud.gateway.route.RouteDefinition;
import org.springframework.cloud.gateway.route.RouteDefinitionWriter;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.stereotype.Service;
import org.springframework.web.util.UriComponentsBuilder;
import reactor.core.publisher.Mono;

import java.net.URI;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * @ClassName : GatewayServiceImpl
 * @Description :
 * @Author : 康仕球
 * @Date: 2020-08-04 21:37
 */
@Service
public class GatewayServiceImpl implements GatewayService {

    @Autowired
    private GatewayDao gatewayDao;

    @Autowired
    private RouteDefinitionWriter routeDefinitionWriter;

    @Autowired
    private ApplicationEventPublisher publisher;

//    public void setApplicationEventPublisher(ApplicationEventPublisher applicationEventPublisher) {
//        this.publisher = applicationEventPublisher;
//    }

    @Override
    public void loadRouter(GatewayDo gatewayDo) {
        RouteDefinition definition = new RouteDefinition();
        Map<String, String> predicateParams = new HashMap<>(8);
        PredicateDefinition predicate = new PredicateDefinition();
        FilterDefinition filterDefinition = new FilterDefinition();
        Map<String, String> fileterParams = new HashMap<>(8);

        URI uri = null;
        // 如果配置路由type 为 0的话 则从注册中心获取服务地址
        if (Constants.ROUTER_TYPE.equals(gatewayDo.getRouteType())) {
            uri = UriComponentsBuilder.fromUriString("lb://" + gatewayDo.getRouteUrl() + "/").build().toUri();
        } else {
            UriComponentsBuilder.fromHttpUrl(gatewayDo.getRouteUrl()).build().toUri();
        }

        // 定义唯一路由ID
        definition.setId(gatewayDo.getRouteId());
        predicate.setName("Path");


        // 路由转发地址
        predicateParams.put("pattern", gatewayDo.getRoutePattern());
        predicate.setArgs(predicateParams);


        // 名称是固定的，路径去前缀
        filterDefinition.setName("StripPrefix");
        fileterParams.put("_genkey_0", "1");
        filterDefinition.setArgs(fileterParams);
        definition.setPredicates(Arrays.asList(predicate));
        definition.setFilters(Arrays.asList(filterDefinition));
        definition.setUri(uri);
        routeDefinitionWriter.save(Mono.just(definition)).subscribe();
        publisher.publishEvent(new RefreshRoutesEvent(this));
    }

    @Override
    public void loadAllRouter() {

        List<GatewayDo> list = gatewayDao.allList();
        for (GatewayDo gdo : list) {
            loadRouter(gdo);
        }

    }

}
